home *** CD-ROM | disk | FTP | other *** search
/ MacFormat 1995 January / macformat-020.iso / Shareware City / Applications / Alpha.5.96 folder / Tcl / SystemCode / c.tcl < prev    next >
Encoding:
Text File  |  1994-08-23  |  5.2 KB  |  202 lines  |  [TEXT/ALFA]

  1. #=============================================================================
  2. # "Electric" C functions.
  3. #=============================================================================
  4.  
  5. # returns the indent string of the line named by 'pos'
  6. proc indentString pos {
  7.     set start [lineStart $pos]
  8.     set end [nextLineStart $pos]
  9.     set text [getText $start $end]
  10.     for {set i 0} {1} {incr i} {
  11.         set c [string index $text $i]
  12.         if {($c != "\ ") && ($c != "\t")} then {
  13.             return [string range $text 0 [expr $i-1]]
  14.         }
  15.     }
  16.     return
  17. }
  18.  
  19.  
  20. # Brace on new line, same indentation. Insert on another new line, indented in.
  21. # First, see if we are on new line.
  22. proc electricCLeft {} {
  23.     global elecLBrace
  24.     deleteText [getPos] [selEnd]
  25.     if {$elecLBrace == "0"} then {
  26.         insertText "\{"
  27.         return
  28.     }
  29.     set pos [getPos]
  30.     set start [lineStart $pos]
  31.     set text [getText $start $pos]
  32.     
  33.     for {set i $start} {$i < $pos} {incr i} {
  34.         set c [lookAt $i]
  35.         if {($c != "\ ") && ($c != "\t")} then {
  36.             set indentation [getText $start $i]
  37.             insertText " \{\r" $indentation "\t"
  38.             return
  39.         }
  40.     }
  41.     set indentation [getText $start $pos]
  42.     insertText "\{\r" $indentation "\t"
  43. }
  44. bind '\{' <s> electricCLeft C
  45. bind '\{' <s> electricCLeft C++
  46.  
  47.  
  48. # Brace on new line, immediate carriage return
  49. proc electricCRight {} {
  50.     global elecRBrace
  51.     deleteText [getPos] [selEnd]
  52.     if {$elecRBrace == "0"} then {
  53.         insertText "\}"
  54.         catch {blink [matchIt "\}" [expr [getPos]-2]]}
  55.         return
  56.     }
  57.     set pos [getPos]
  58.     set start [lineStart $pos]
  59.     
  60.     if {[catch {matchIt "\}" [expr $pos-1]} matched]} {
  61.         beep
  62.         return
  63.     }
  64.     set text [getText [lineStart $matched] $matched]
  65.     regexp {^[     ]*} $text indentation
  66.     for {set i $start} {$i < $pos} {incr i} {
  67.         set c [lookAt $i]
  68.         if {($c != "\ ") && ($c != "\t")} then {
  69.             insertText "\r" $indentation "\}\r" $indentation
  70.             blink $matched
  71.             return
  72.         }
  73.     }
  74.     set text [set indentation]\}\r$indentation
  75.     replaceText $start $pos $text
  76.     goto [expr {$start + [string length $text]}]
  77.     blink [matchIt "\}" [expr $start-2]]
  78. }
  79. bind '\}' <s> electricCRight C
  80. bind '\}' <s> electricCRight C++
  81.  
  82.  
  83. # Brace on new line, immediate carriage return. We don't do our electric stuff
  84. # if we are in the middle of a for statement.
  85. proc electricCSemi {} {
  86.     global electricSemi
  87.     deleteText [getPos] [selEnd]
  88.     if {$electricSemi == "0"} then {
  89.         insertText ";"
  90.         return
  91.     }
  92.     set pos [getPos]
  93.     set start [lineStart $pos]
  94.     set text [getText $start $pos]
  95.     
  96.     if {[string first "for" $text] != "-1"} {
  97.         set lefts 0
  98.         set rights 0
  99.         set len [string length $text]
  100.         for {set i 0} {$i < $len} {incr i} {
  101.             case [string index $text $i] in {
  102.                 "("    { incr lefts }
  103.                 ")"    { incr rights }
  104.             }
  105.         }
  106.         global globs
  107.         set globs [list $lefts $rights $len]
  108.         if {$lefts != $rights} {
  109.             insertText ";"
  110.             return
  111.         }
  112.     }
  113.     
  114.     insertText ";\r" [indentString $pos]
  115. }
  116. bind '\;' electricCSemi C
  117. bind '\;' electricCSemi C++
  118.  
  119.     
  120.  
  121. #================================================================================
  122.  
  123. proc CMarkFile {} {
  124.     global CmodeVars
  125.     set pos 0
  126.     while {![catch {search -f 1 -r 1 -m 0 -i 0 $CmodeVars(funcExpr) $pos} res]} {
  127.         set start [lindex $res 0]
  128.         set end [expr [lindex $res 1] + 1]
  129.         if {[regexp {([a-zA-Z0-9:_]+)[ \t]*\(} [getText $start $end] dummy word]} {
  130.             set inds($word) [lineStart [expr $start - 1]]
  131.         }
  132.         set pos $end
  133.     }
  134.     if {[info exists inds]} {
  135.         foreach f [lsort [array names inds]] {
  136.             set next [nextLineStart $inds($f)]
  137.             setNamedMark $f $inds($f) $next $next
  138.         }
  139.     }
  140. }
  141. proc CMarkFile {} {
  142.     global CmodeVars
  143.     set pos 0
  144.     while {![catch {search -f 1 -r 1 -m 0 -i 0 $CmodeVars(funcExpr) $pos} res]} {
  145.         set start [lindex $res 0]
  146.         set end [expr [lindex $res 1] + 1]
  147.         set text [getText $start $end]
  148.         if {[regexp {([a-zA-Z0-9:_]+)[ \t]*\(} $text dummy word]} {
  149.             set tmp [expr $start + [string first $word $text]]
  150.             set inds($word) "$tmp [expr $tmp + [string length $word]]"
  151.         }
  152.         set pos $end
  153.     }
  154.     if {[info exists inds]} {
  155.         foreach f [lsort -ignore [array names inds]] {
  156.             set res $inds($f)
  157.             setNamedMark $f [lineStart [lindex $res 0]] [lindex $res 0] [lindex $res 1]
  158.         }
  159.     }
  160. }
  161.  
  162.     
  163. #The previous version would not find things like     void    *ThisFunc( xxx ) due to the asterisk
  164. #I also truncated the pattern.  The rest is not necessary and intrusive as far as I can tell   
  165. proc C++MarkFile {} {
  166.     set pos 0
  167.     while {![catch {search -f 1 -r 1 -m 0 -i 0 {^([^ \t\(#\r/@].*[ \t]+)?\*?([A-Za-z0-9:~_]+)[ \t\r]*\(} $pos} res]} {
  168.         set start [lindex $res 0]
  169.         set end [expr [lindex $res 1] + 1]
  170.         set thistext [getText $start $end]
  171.         #regexp doesn't like carriage returns
  172.         regsub -all "\r" $thistext " " thistext
  173.         #regexp doesn't like tabs either
  174.         regsub -all "\t" $thistext " " thistext
  175.         #if the open paren was the last character on the line the selected text included the last carriage return as well
  176.         #trim this off now that it is changed into a space
  177.         set thistext [string trimright $thistext]
  178.         if {[regexp {([a-zA-Z0-9:~_]+)[ \t]*\(} $thistext dummy word]} {
  179.             set inds($word) [lineStart [expr $start - 1]]
  180.         }
  181.         set pos $end
  182.     }
  183.     if {[info exists inds]} {
  184.         foreach f [lsort -ignore [array names inds]] {
  185.             set next [nextLineStart $inds($f)]
  186.             setNamedMark $f $inds($f) $next $next
  187.         }
  188.     }
  189. }
  190.  
  191.     
  192. proc setC++Mode {} {
  193.     changeMode "C++"
  194. }
  195.  
  196.  
  197.  
  198. source "$HOME:Tcl:SystemCode:think.tcl"
  199.  
  200. proc dummyC {} {}
  201. proc dummyC++ {} {}
  202.